package view;

import android.animation.ValueAnimator;
import android.content.Context;
import android.os.Handler;
import android.util.AttributeSet;
import android.view.MotionEvent;
import android.view.ViewConfiguration;
import android.view.ViewGroup;
import android.view.animation.AccelerateDecelerateInterpolator;

/**
 * Created by ilioili on 2015/3/24.
 */
public class MyScrollView extends ViewGroup {
    private final int mTouchSlop;
    float firstFingerY;
    float lastPosition;
    private int downViewHeight = 100;
    private int prePosition;
    private ScrollListener scrollListener;
    private int upViewHeight = 100;
    private int position = upViewHeight;

    public MyScrollView(Context context, AttributeSet attrs) {
        super(context, attrs);
        mTouchSlop = ViewConfiguration.get(context).getScaledTouchSlop();
        setOffset((int) (context.getResources().getDisplayMetrics().density * 50), (int) (context.getResources().getDisplayMetrics().density * 35));
    }

    private void setOffset(int upViewHeight, int downViewHeight) {
        this.upViewHeight = upViewHeight;
        this.downViewHeight = downViewHeight;
        this.position = upViewHeight + downViewHeight;
    }

    @Override
    public boolean onInterceptTouchEvent(MotionEvent ev) {
        return true;
    }

    @Override
    protected void onLayout(boolean changed, int l, int t, int r, int b) {
        getChildAt(0).layout(0, position, getMeasuredWidth(), position + getChildAt(0).getMeasuredHeight());
        //        scrollTo(0, position);
    }

    @Override
    public boolean onTouchEvent(MotionEvent event) {
        switch (event.getAction()) {
            case MotionEvent.ACTION_DOWN:
                lastPosition = prePosition = position;
                firstFingerY = event.getY();
                break;
            case MotionEvent.ACTION_MOVE:
                position = (int) (lastPosition + event.getY() - firstFingerY);
                if (position <= downViewHeight) {
                    position = downViewHeight;
                } else if (position >= upViewHeight + downViewHeight) {
                    position = upViewHeight + downViewHeight;
                }
                break;
            case MotionEvent.ACTION_UP:
                if (position != downViewHeight + upViewHeight && position != downViewHeight) {
                    event.setAction(MotionEvent.ACTION_CANCEL);
                    ValueAnimator animator = ValueAnimator.ofInt(position, downViewHeight + upViewHeight);
                    animator.setDuration(250);
                    animator.setInterpolator(new AccelerateDecelerateInterpolator());
                    animator.addUpdateListener(new ValueAnimator.AnimatorUpdateListener() {
                        @Override
                        public void onAnimationUpdate(ValueAnimator animation) {
                            int value = (int) animation.getAnimatedValue();
                            position = value;
                            getChildAt(0).layout(0, position, getMeasuredWidth(), position + getMeasuredHeight() - upViewHeight);
                            scrollListener.onScroll(position, upViewHeight);
                        }
                    });
                    animator.start();
                }

                break;
        }
        if (prePosition != position) {
            //            scrollTo(0, -position);
            getChildAt(0).layout(0, position, getMeasuredWidth(), position + getChildAt(0).getMeasuredHeight());
            scrollListener.onScroll(position, upViewHeight);
        }
        event.setLocation(event.getX(), event.getY() - position);
        //        if(position>upViewHeight && position<upViewHeight+downViewHeight && MotionEvent.ACTION_MOVE==event.getAction()){
        //            event.setAction(MotionEvent.ACTION_DOWN);
        //        }
        getChildAt(0).dispatchTouchEvent(event);
        prePosition = position;
        return true;
    }

    @Override
    protected void onMeasure(int widthMeasureSpec, int heightMeasureSpec) {
        super.onMeasure(widthMeasureSpec, heightMeasureSpec);
        int height = MeasureSpec.getSize(heightMeasureSpec);
        measureChildren(widthMeasureSpec, MeasureSpec.makeMeasureSpec(height - downViewHeight, MeasureSpec.EXACTLY));
    }

    public void setPosition(int p) {
        position = p;
        new Handler().post(new Runnable() {
            @Override
            public void run() {
                getChildAt(0).layout(0, position, getMeasuredWidth(), position + getChildAt(0).getMeasuredHeight());
                requestLayout();
            }
        });

        //        scrollTo(0, position);
        //        getChildAt(0).layout(0, position, getMeasuredWidth(), getMeasuredHeight() + position);
    }

    public void setScrollListener(ScrollListener listener) {
        scrollListener = listener;
    }

    public interface ScrollListener {
        void onScroll(int curPosition, int total);
    }
}
